package net.mayee.alice.service.admin.account;

import jodd.props.Props;
import net.mayee.alice.common.Definiens;
import net.mayee.alice.dao.admin.account.RoleDao;
import net.mayee.alice.dao.admin.account.UserDao;
import net.mayee.alice.entity.admin.account.Role;
import net.mayee.alice.entity.admin.account.User;
import net.mayee.alice.entity.admin.account.UserRole;
import net.mayee.alice.web.utils.UUIDGenerator;
import net.mayee.common.AliceHelper;
import net.mayee.common.utils.Encodes;
import net.mayee.leo.LeoEncrypt;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;

@Transactional
@Service("UserService")
public class UserService {

    @Autowired
    private UserDao userDao;
    @Autowired
    private RoleDao roleDao;

    public User getUser(String uuid) {
        return userDao.get(uuid);
    }

    public void resetPassword(User user) {
        encryptPassword(user);
        userDao.updatePassword(user);
    }

    public void insertUser(User user, String roleString) {
        user.setUuid(UUIDGenerator.getUUID());
        encryptPassword(user);
        user.setStatusCode(Definiens.STATUS_CODE_USER_NORMAL);
        userDao.insert(user);

        String[] roleKeys = roleString.split(",");
        for (String roleKey : roleKeys) {
            Role r = roleDao.getByRoleKey(roleKey);
            userDao.insertUserRole(new UserRole(r.getUuid(), user.getUuid()));
        }
    }

    public void updateUser(User user, String roleString) {
        userDao.update(user);

        if (roleString != null) {
            /* remove all roles by user */
            userDao.removeRolesByUser(user.getUuid());

            /* add new roles */
            String[] roleKeys = roleString.split(",");
            for (String roleKey : roleKeys) {
                Role r = roleDao.getByRoleKey(roleKey);
                userDao.insertUserRole(new UserRole(r.getUuid(), user.getUuid()));
            }
        }
    }

    public void removeUser(String uid) {
        userDao.removeRolesByUser(uid);
        userDao.remove(uid);
    }

    public void removeRolesByUser(String uid) {
        userDao.removeRolesByUser(uid);
    }

    public int count(Map<String, Object> parameters) {
        return userDao.count(parameters);
    }

    public List<User> searchByLimit(Map<String, Object> parameters) {
        return userDao.searchByLimit(parameters);
    }

    public User getByLoginName(String loginName) {
        return userDao.getByLoginName(loginName);
    }

    public List<User> getAllNoAdmin() {
        return userDao.getAllNoAdmin();
    }

    public List<User> getUsersByRole(String uuid) {
        return userDao.getUsersByRole(uuid);
    }

    public List<String> getNamesByRole(String uuid) {
        List<String> namesList = new ArrayList<String>();
        List<User> userList = userDao.getUsersByRole(uuid);
        for (User user : userList) {
            namesList.add(user.getLoginName());
        }
        return namesList;
    }

    private void encryptPassword(User user) {
        Props props = AliceHelper.getInstance().getJoddProps();
        byte[] salt = LeoEncrypt.generateSalt(Integer.parseInt(props.getValue("encrypt.salt.size")));
        user.setSalt(Encodes.encodeHex(salt));

        byte[] hashPassword = LeoEncrypt.sha1(user.getPlainPassword()
                .getBytes(), salt, Integer.parseInt(props.getValue("encrypt.hash.interations")));
        user.setLoginPassword(Encodes.encodeHex(hashPassword));
    }

}
